﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace BoYuanCore.CoreCodeTemplates.DBMappingRules
{
    /// <summary>
    /// 数据类型对应规则
    /// </summary>
    public class DataTypeMapping
    {
        public class Mssql
        {
            public static Dictionary<string, string> GetBaseDataType()
            {
                Dictionary<string, string> dic = new Dictionary<string, string>();
                //数据库                  C#  
                dic["int"] = "System.Int32";
                dic["text"] = "System.String";
                dic["bigint"] = "System.Int64";
                dic["binary"] = "System.Byte[]";
                dic["bit"] = "System.Boolean";
                dic["char"] = "System.String";
                dic["datetime"] = "System.DateTime";
                dic["decimal"] = "System.Decimal";
                dic["float"] = "System.Double";
                dic["image"] = "System.Byte[]";
                dic["money"] = "System.Decimal";
                dic["nchar"] = "System.String";
                dic["ntext"] = "System.String";
                dic["numeric"] = "System.Decimal";
                dic["nvarchar"] = "System.String";
                dic["real"] = "System.Single";
                dic["smalldatetime"] = "System.DateTime";
                dic["smallint"] = "System.Int16";
                dic["smallmoney"] = "System.Decimal";
                dic["timestamp"] = "System.DateTime";
                dic["tinyint"] = "System.Byte";
                dic["uniqueidentifier"] = "System.Guid";
                dic["varbinary"] = "System.Byte[]";
                dic["varchar"] = "System.String";
                dic["variant"] = "System.Object";
                return dic;
            }

            public static string GetConvertString(string dbTypeName)
            {
                string result = string.Empty;
                switch (dbTypeName.ToLower())
                {
                    #region Int
                    case "int":
                        result = "Convert.ToInt32";
                        break;
                    #endregion

                    #region String
                    case "nchar":
                    case "char":
                    case "ntext":
                    case "nvarchar":
                    case "varchar":
                    case "text":
                        result = "Convert.ToString";
                        break;
                    #endregion

                    #region Long
                    case "bigint":
                        result = "Convert.ToInt64";
                        break;
                    #endregion

                    #region Bool
                    case "bit":
                        result = "Convert.ToBoolean";
                        break;

                    #endregion

                    #region Datetime
                    case "timestamp":
                    case "smalldatetime":
                    case "datetime":
                    case "date":
                    case "datetime2":
                        result = "Convert.ToDateTime";
                        break;
                    #endregion

                    #region Decimal
                    case "smallmoney":
                    case "single":
                    case "numeric":
                    case "money":
                    case "decimal":
                        result = "Convert.ToDecimal";
                        break;
                    #endregion

                    #region Double
                    case "float":
                        result = "Convert.ToDouble";
                        break;
                    #endregion

                    #region Byte[]
                    case "varbinary":
                    case "binary":
                    case "image":
                        result = "byte[]";
                        break;
                    #endregion

                    #region Float
                    case "real":
                        result = "Convert.ToSingle";
                        break;
                    #endregion

                    #region Short
                    case "smallint":
                        result = "Convert.ToInt16";
                        break;
                    #endregion

                    #region Byte
                    case "tinyint":
                        result = "Convert.ToByte";
                        break;

                    #endregion

                    #region Guid
                    case "uniqueidentifier":
                        result = "Guid.Parse";
                        break;
                    #endregion

                    #region Null
                    default:
                        result = null;
                        break;
                        #endregion
                }
                return result;
            }
        }


        public class Csharp
        {
            //参考 https://docs.microsoft.com/zh-cn/dotnet/csharp/language-reference/builtin-types/built-in-types

            /// <summary>
            /// 内置类型转换关系列表
            /// </summary>
            /// <returns></returns>
            public static Dictionary<string, string> GetBaseTypeInfos()
            {
                //.NET 类型 对应 C# 类型关键字
                //System.Int32 对应 int
                Dictionary<string, string> dic = new Dictionary<string, string>();
                //.NET 类型             C# 类型关键字
                dic["System.Boolean"]  = "bool";
                dic["System.Byte"]     = "byte";
                dic["System.SByte"]    = "sbyte";
                dic["System.Char"]     = "char";
                dic["System.Decimal"]  = "decimal";
                dic["System.Double"]   = "double";
                dic["System.Single"]   = "float";
                dic["System.Int32"]    = "int";
                dic["System.UInt32"]   = "uint";
                dic["System.Int64"]    = "long";
                dic["System.UInt64"]   = "ulong";
                dic["System.Int16"]    = "short";
                dic["System.UInt16"]   = "ushort";

                //下面引用类型。上面是值类型
                dic["System.Object"]   = "object";
                dic["System.String"]   = "string";

                return dic;
            }

            /// <summary>
            /// 内置类型,根据.NET 类型转成 C# 类型关键字(例如System.Int32 转成 int)
            /// </summary>
            /// <param name="netName">.NET 类型(例如System.Int32)</param>
            /// <returns></returns>
            public static string GetCsharpKeyword(string netName)
            {
                bool isArray = netName.Contains("[]");//是否为数组类型
                string keyStr = "System." + netName.Replace("System.", "");//类似Int32 统一改成 System.Int32
                keyStr = keyStr.Replace("[]", "");//去掉数组声明

                Dictionary<string, string> dict = GetBaseTypeInfos();
                if (!dict.ContainsKey(keyStr))//不包含此key
                {
                    //System.DateTime System.Guid 等。
                    return netName.Replace("System.", "");
                }

                string csharpKeyword = GetBaseTypeInfos()[keyStr];
                return isArray? csharpKeyword+"[]": csharpKeyword;
            }

            
        }

        /// <summary>
        /// 获取类或属性名称(首字母大写)
        /// </summary>
        /// <param name="tableName">表名称或字段名称</param>
        /// <returns></returns>
        public static string GetFormatName(string tableName)
        {
            return tableName.Substring(0, 1).ToUpper() + tableName.Substring(1);//首字母大写
        }
    }
}
/* //创建 测试类型的sql

 CREATE TABLE [dbo].[tb](
	[id] [int] IDENTITY(1,1) NOT NULL,
	[title] [nvarchar](100) NOT NULL,
	[realCol] [real] NULL,
	[floatCol] [float] NULL,
	[datetimeCol] [datetime] NULL,
	[tinyintCol] [tinyint] NULL,
	[nvarcharCol] [nvarchar](100) NULL,
	[bigintCol] [bigint] NULL,
	[decimalCol] [decimal](18, 0) NULL,
	[moneyCol] [money] NULL,
	[smallintCol] [smallint] NULL,
	[bitCol] [bit] NULL,
 CONSTRAINT [PK_tb] PRIMARY KEY CLUSTERED 
(
	[id] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY]
) ON [PRIMARY]

 */
